package com.sky.chapter3.executor;

import java.util.Date;
import java.util.concurrent.*;

/**
 * @author : wushikai
 * <p>
 * date : 2022-06-29
 */

public class ThreadPoolExecutorDemo {


    static class MyRunnable implements Runnable {

        private String command;

        public MyRunnable(String s) {
            this.command = s;
        }

        @Override
        public void run() {
            System.out.println(Thread.currentThread().getName() + " Start. Time = " + new Date());
            processCommand();
            System.out.println(Thread.currentThread().getName() + " End. Time = " + new Date());
        }

        private void processCommand() {
            try {
                Thread.sleep(5000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }

        @Override
        public String toString() {
            return this.command;
        }
    }


    private static final int CORE_POOL_SIZE = 5;
    private static final int MAX_POOL_SIZE = 10;
    private static final int QUEUE_CAPACITY = 100;
    private static final Long KEEP_ALIVE_TIME = 1L;

    public static void main(String[] args) {


        //ExecutorService executorService = Executors.newFixedThreadPool(CORE_POOL_SIZE);  不推荐
        //阿里巴巴推荐的创建线程池的方式, 通过ThreadPoolExecutor构造函数自定义参数创建



        /*
        *
        *corePoolSize -保留在池中的线程数，即使它们是空闲的，除非设置了allowCoreThreadTimeOut

        maximumPoolSize—池中允许的最大线程数

        keepAliveTime——当线程数量大于核心时，这是多余空闲线程在终止前等待新任务的最大时间。

        unit—keepAliveTime参数的时间单位

        workQueue——在任务执行之前用于保存任务的队列。这个队列将只保存execute方法提交的Runnable任务。

        处理程序——当执行因线程边界和队列容量达到而被阻塞时使用的处理程序
        *
        * */
        ThreadPoolExecutor executor = new ThreadPoolExecutor(
                CORE_POOL_SIZE,
                MAX_POOL_SIZE,
                KEEP_ALIVE_TIME,
                TimeUnit.SECONDS,
                new ArrayBlockingQueue<>(QUEUE_CAPACITY),
                new ThreadPoolExecutor.CallerRunsPolicy());

        for (int i = 0; i < 10; i++) {
            //创建WorkerThread对象（WorkerThread类实现了Runnable 接口）
            Runnable worker = new MyRunnable("" + i);
            //执行Runnable
            executor.execute(worker);
        }
        //终止线程池
        executor.shutdown();
        while (!executor.isTerminated()) {
        }
        System.out.println("Finished all threads");
    }


}


